#pragma once
#include <iostream>

// 飞行基类
class FlyBehavior
{
public:
  FlyBehavior()
  {}
  virtual void Fly(){}
};

// 叫声基类
class QuackBehavior
{
public:
    virtual void Quack(){}
};


class SwimBehavior
{
  public:
    virtual void Swim(){}
};

// 鸭子基类
class Duck
{
protected:
  FlyBehavior* _flyBehavior;
  QuackBehavior* _quackBehavior;
  SwimBehavior* _swimBehavior;

public:
  Duck(FlyBehavior* fb, QuackBehavior* qb, SwimBehavior* sb)
    :_flyBehavior(fb), _quackBehavior(qb), _swimBehavior(sb)
  {}

  Duck()
    :_flyBehavior(nullptr), _quackBehavior(nullptr)
  {}

  // 注意：虚函数需要定义，不定义会找不到
  virtual void Display(){}

  void SetterSwim(SwimBehavior* sb)
  {
    if(sb != nullptr)
      _swimBehavior = sb;
  }

  void SetterFly(FlyBehavior* fb)
  {
    if(fb != nullptr)
      _flyBehavior = fb;
  }
  
  void SetterQuack(QuackBehavior* qb)
  {
    if(qb != nullptr)
      _quackBehavior = qb;
  }

  void PerformFly()
  {
    if(_flyBehavior != nullptr)
      _flyBehavior->Fly();
  }
  
  void PerformQuack()
  {
    if(_quackBehavior != nullptr)
      _quackBehavior->Quack();
  }

  void PerformSwim()
  {
    if(_swimBehavior != nullptr)
      _swimBehavior->Swim();
  }
};

